跳到主要内容

Linux 进程状态监控

检查当前进程

ps aux

Linux 的进程状态

(注意!进程不是服务)

linux上进程有5种状态:

  1. 运行(正在运行或在运行队列中等待)
  2. 中断(休眠中,受阻,在等待某个条件的形成或接受到信号)
  3. 不可中断(收到信号不唤醒和不可运行,进程必须等待直到有中断发生)
  4. 僵死(进程已终止,但进程描述符存在,直到父进程调用 wait4() 系统调用后释放)
  5. 停止(进程收到SIGSTOP, SIGSTP, SIGTIN, SIGTOU信号后停止运行运行)

ps工具标识进程的5种状态码:

  • D 不可中断 uninterruptible sleep (usually IO)
  • R 运行 runnable (on run queue)
  • S 中断 sleeping
  • T 停止 traced or stopped
  • Z 僵死 a defunct (”zombie”) process

常见的关键字

  • PID:进程号,每个进程独一无二的标识符(关闭进程需要使用)
  • TTY:终端所属,表明进程产生于哪一个终端,对于多用户使用的Linux服务器有区分用户的功能
  • TIME:进程运行了多久
  • CMD:进程源于哪个程序
  • VIRT:进程占用的虚拟内存
  • RES:进程占用的物理内存
  • USER:进程所有者
  • TYPE:协议类型
  • DEVICE:端口号
  • SIZE/OFF:偏移
  • NODE:协议名
  • NAME:节点名
  • VSZ: 占用的虚拟记忆体大小

top 任务监视器

top 类似于 Windows 的任务管理器。

top 是一个动态显示过程,即可以通过用户按键来不断刷新当前状态。如果在前台执行该命令,它将独占前台,直到用户终止该程序为止。

image.png

命令格式:

top [参数]

命令参数:

-b 批处理
-c 显示完整的治命令
-I 忽略失效过程
-s 保密模式
-S 累积模式

-i<时间> 设置间隔时间

-u<用户名> 指定用户名

-p<进程号> 指定进程

-n<次数> 循环显示的次数

ps 命令的常见用法

Linux 中的 ps 命令是 Process Status 的缩写。ps 命令用来列出系统中当前运行了哪些进程。列出的是当前那些进程的快照,如果想要动态的显示进程信息,就可以使用 top 命令。

ps 的参数非常多,在此仅列出几个常用的参数并大略介绍含义

  • -A 列出所有的进程
  • -w 显示加宽可以显示较多的资讯
  • -au 显示较详细的资讯
  • -aux 显示所有包含其他使用者的行程
ps -ef # 列出所有用户所有终端的所有进程

ps -ef | grep -i "nginx"

ps -efH # 按乔木状列出所有进程,有的进程是某些进程的子进程

ps -u username # 列出特定用户运行的进程

ps aux # 查看服务进程(后台服务)

ps aux | grep "关键字" # 关键字查找进程

top # 显示当前内存占用情况

jobs -l # 显示后台进程

ps -aux 输出字段的意义

au(x) 输出格式 :

USER PID %CPU %MEM VSZ RSS TTY STAT START TIME COMMAND
  • USER: 行程拥有者
  • PID: pid
  • %CPU: 占用的 CPU 使用率
  • %MEM: 占用的记忆体使用率
  • VSZ: 占用的虚拟记忆体大小
  • RSS: 占用的记忆体大小
  • TTY: 终端的次要装置号码 (minor device number of tty)

image64a3b58172c0ffc3.png

ps 和 jobs 区别

jobs:该命令用于查看当前终端后台运行的任务。 ps:该命令用于查看瞬间进程的动态。

一般来说 ps 是看进程状态之类的,jobs 是看工作号的

检查开了几个子线程

问题: 我的程序在其内部创建并执行了多个线程,我怎样才能在该程序创建线程后监控其中单个线程?我想要看到带有它们名称的单个线程详细情况(如,CPU/内存使用率)。

线程是现代操作系统上进行并行执行的一个流行的编程方面的抽象概念。当一个程序内有多个线程被叉分出用以执行多个流时,这些线程就会在它们之间共享特定的资源(如,内存地址空间、打开的文件),以使叉分开销最小化,并避免大量高成本的 IPC(进程间通信)通道。这些功能让线程在并发执行时成为一个高效的机制。

这里提供了在 Linux 上显示某个进程的线程的几种方式。

1、利用进程名获取进程号(以自己创建的进程 middlebaby 为例)

ps -ef|grep middlebaby|grep -v "grep"|awk '{print $2}'

grep 的输出都会有 grep 自身这个进程在,用 grep -v "grep" 可以把这一行干掉,然后 awk '{print $2}' 就是打印第二列数字,即 16154 (这里因为是通过 makefile 启动的,所以有两个进程)

awk 是处理文本文件的一个应用程序,几乎所有 Linux 系统都自带这个程序。它依次处理文件的每一行,并读取里面的每一个字段。对于日志、CSV 那样的每行格式相同的文本文件,awk 可能是最方便的工具。

利用进程号查看该进程下的线程

ps -eLf|grep 16154|grep -v "grep"

第四列就是线程号

ps -T -p 16154

输出如下:(SPID 即线程号)

利用 top -H -p 16154 查看线程 cpu 利用率

第二行(Threads):总共11个线程,0个正在执行,11个睡眠,0个stopped, 0个zombie(僵尸), %CPU%MEM 即cpu占有率和内存占有率,其他字段含义参考top命令

2、使用 pstree 命令树状图显示

pstree -p 16154

检查开了几个子进程

使用 pgrep 命令

pgrep -P $parent_pid

pgrep 允许你基于给定条件来查找正在运行的程序的进程 ID。它可以是进程名字的全称或者一部分,进程运行者,或者其他属性。

或者使用 ps 的 ppid flag

ps --ppid $parent_pid

References